package com.indi.gulimall.member.service.impl;

import com.alibaba.fastjson.JSON;
import com.alibaba.fastjson.JSONObject;
import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
import com.baomidou.mybatisplus.core.metadata.IPage;
import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
import com.indi.common.enums.BizCodeEnum;
import com.indi.common.exception.Assert;
import com.indi.common.to.LoginTO;
import com.indi.common.to.RegisterTO;
import com.indi.common.utils.HttpUtils;
import com.indi.common.utils.PageUtils;
import com.indi.common.utils.Query;
import com.indi.gulimall.member.dao.MemberDao;
import com.indi.gulimall.member.entity.MemberEntity;
import com.indi.gulimall.member.entity.MemberLevelEntity;
import com.indi.gulimall.member.service.MemberLevelService;
import com.indi.gulimall.member.service.MemberService;
import org.apache.http.HttpResponse;
import org.apache.http.util.EntityUtils;
import org.springframework.security.crypto.bcrypt.BCryptPasswordEncoder;
import org.springframework.stereotype.Service;

import javax.annotation.Resource;
import java.util.HashMap;
import java.util.List;
import java.util.Map;


@Service("memberService")
public class MemberServiceImpl extends ServiceImpl<MemberDao, MemberEntity> implements MemberService {
    @Resource
    private MemberLevelService memberLevelService;

    @Override
    public PageUtils queryPage(Map<String, Object> params) {
        IPage<MemberEntity> page = this.page(
                new Query<MemberEntity>().getPage(params),
                new QueryWrapper<MemberEntity>()
        );

        return new PageUtils(page);
    }

    @Override
    public void checkUsernameUnique(String userName) {
        List<MemberEntity> members = this.list(new QueryWrapper<MemberEntity>().eq("username", userName));
        Assert.isNullList(members, BizCodeEnum.USERNAME_EXIST_EXCEPTION);
    }

    @Override
    public void checkPhoneNumUnique(String phoneNum) {
        List<MemberEntity> members = this.list(new QueryWrapper<MemberEntity>().eq("mobile", phoneNum));
        Assert.isNullList(members, BizCodeEnum.PHONE_NUM_EXIST_EXCEPTION);
    }

    @Override
    public MemberEntity login(LoginTO loginTO) {
        MemberEntity member = this.getOne(new QueryWrapper<MemberEntity>().eq("username", loginTO.getUserAccount()).or()
                .eq("mobile", loginTO.getUserAccount()));
        Assert.notNull(member, BizCodeEnum.LOGIN_EXCEPTION);

        String password = member.getPassword();
        BCryptPasswordEncoder passwordEncoder = new BCryptPasswordEncoder();
        boolean result = passwordEncoder.matches(loginTO.getPassword(), password);
        Assert.isTrue(result, BizCodeEnum.LOGIN_EXCEPTION);
        return member;
    }

    @Override
    public MemberEntity giteeLogin(String giteeInfo) throws Exception {
        // 拿到accesstoken，获取用户基本信息
        JSONObject baseJson = JSON.parseObject(giteeInfo);
        Map<String, String> params = new HashMap<>();
        String accessToken = baseJson.getString("access_token");
        String expiresIn = baseJson.getString("expires_in");
        params.put("access_token", accessToken);
        HttpResponse response = HttpUtils.doGet("https://gitee.com", "/api/v5/user", "get", null, params);

        Assert.isTrue(response.getStatusLine().getStatusCode() == 200, BizCodeEnum.OAUTH2_GITEE_EXCEPTION);

        String s = EntityUtils.toString(response.getEntity());
        JSONObject jsonObject = JSON.parseObject(s);
        String id = jsonObject.getString("id");

        MemberEntity member = this.getOne(new QueryWrapper<MemberEntity>().eq("social_uid", "gitee" + "_" + id));
        if (member != null) {
            // 说明已经注册过，更新令牌、令牌过期时间
            MemberEntity newMember = new MemberEntity();
            newMember.setId(member.getId());
            newMember.setAccessToken(accessToken);
            newMember.setExpiresIn(expiresIn);
            this.updateById(member);
            return member;
        } else {
            // 第一次登录，需要注册
            MemberEntity newMember = new MemberEntity();
            newMember.setSocialUid("gitee" + "_" + id);
            newMember.setNickname(jsonObject.getString("name"));
            newMember.setAccessToken(accessToken);
            newMember.setExpiresIn(expiresIn);
            this.save(newMember);
            return newMember;
        }
    }

    @Override
    public void register(RegisterTO registerTO) {
        MemberEntity member = new MemberEntity();

        // 设置会员的默认等级，需要去数据库查
        MemberLevelEntity memberLevel = memberLevelService.getDefaultLevel();
        member.setLevelId(memberLevel.getId());

        // 检查用户名是否唯一
        this.checkUsernameUnique(registerTO.getUserName());

        // 检查手机号是否唯一
        this.checkPhoneNumUnique(registerTO.getPhoneNum());

        member.setUsername(registerTO.getUserName());
        member.setMobile(registerTO.getPhoneNum());

        // 密码加密存储
        BCryptPasswordEncoder passwordEncoder = new BCryptPasswordEncoder();
        String encodePassword = passwordEncoder.encode(registerTO.getPassword());
        member.setPassword(encodePassword);
        this.save(member);
    }

}